//
//  netWorkTools.swift
//  我的微博
//
//  Created by 杨庆 on 15/10/12.
//  Copyright © 2015年 双元班. All rights reserved.
//

import UIKit
import AFNetworking
/// 错误的类别标记
private let HMErrorDomainName = "com.itheima.error.network"
//网络的访问的错误的信息---枚举,是定义的一组类似的值;
//swift 中的枚举可以定义的函数和属性,跟类是有一点相像的;
private enum HMNetWorkError: Int {
    case emptydataError = -1
    case emptyTokenError = -2
    //错误的描述;
    //注意的是 这里的self 就是 指的枚举的类型
    private var errorDescrption: String{
        switch self {
        case.emptydataError: return "空数据"
        case.emptyTokenError: return "token为空"
        }
      }
    //根据枚举的类型,返回对应的错误的信息,nserror 的实例化的方法就是要 一个domain
    private func error() -> NSError {
        return NSError(domain: HMErrorDomainName, code: rawValue, userInfo: [HMErrorDomainName: errorDescrption])
      }
    }
//网络的访问的方法
private enum HMNetWorkMethod: String{
    case GET = "GET"
    case POST = "POST"
}
class netWorkTools: AFHTTPSessionManager {
    //应用信息的回调
    private let clientId = "1017273071"
    private let appSecret = "836af0ab24b946375a6aae4d3c1f73f0"
    let redirectUri = "http://www.baidu.com"
    //书写单例;
    static let sharedTool : netWorkTools = {
        let baseURL = NSURL(string:"https://api.weibo.com/")!
        let tools = netWorkTools(baseURL: baseURL)
        tools.responseSerializer.acceptableContentTypes = NSSet(objects:"application/json", "text/json", "text/javascript", "text/plain") as Set<NSObject>
        return tools
    }()
    /// 检查并且 生成一个token的字典
    private func tokenDict(finished : HMNetFinishedCallBack) ->[String : AnyObject]?{
        //判断 token是否存在
        if UserAccount.sharedAccount?.access_token == nil{
            //应该有一个错误的回调,不应该的是,直接的放回,这样控件一直是再转菊花;
            //添加一个 错误的回调, token 为空;
            let error = HMNetWorkError.emptyTokenError.error()
            print(error)
            finished(result: nil, error:error)
            return nil
        }
        //否则的是 ,就是成功的生成的 token
        return ["access_token" : UserAccount.sharedAccount!.access_token!]
    }
    //MARK:-加载微博的数据;
    func loadStatus(finished : HMNetFinishedCallBack) {
        //判断 token 是否存在,为nil就直接的返回
        //guard 是swift2.0 的新语法,跟 if get 是正好相反的
        //let 获取的变量,后续可以直接的使用,而且一定不为空
        guard let params = tokenDict(finished)else{
            //params 在此为空,就直接返回
            return
        }
        //代码能够运行到此,params 是一定有值的,它能自动的筛选
        let urlString = "2/statuses/home_timeline.json"
        request(HMNetWorkMethod.GET, urlString: urlString, pragma: params, finished: finished)
    }
    //MARK:-加载用户数据;
    /// 加载用户信息
    ///
    /// - parameter uid:      用户代号字符串
    /// - parameter finished: 完成回调
    func loadUserInfo(uid : String,finished : HMNetFinishedCallBack){
        //先要求的是判断token 是否是存在;
        //guard 还可以应用 var 这样的话就可以进行的拼接
        guard var params = tokenDict(finished)else{
            //params 在此为空,就直接返回
            return
        }

        let uslString = "/2/users/show.json"
        //直接给 params 添加了一个字典
        params["uid"] = uid
        //发送网络的请求(就是开始进行调用我们的封装的 get 的方法)
        //提示: 如果参数不正确,首先要应用 option + click 来确认参数类
        request(HMNetWorkMethod.GET, urlString: uslString, pragma: params, finished: finished)
    }
    //MARK:-oAuth 的授权;
    func oauthUrl() -> NSURL {
    //返回的是 oAuth的授权的界面
    //其中的首地址 是要求后端的服务员要求提供的;
    let urlString = "https://api.weibo.com/oauth2/authorize?client_id=\(clientId)&redirect_uri=\(redirectUri)"
        return NSURL(string :urlString)!
    }
    //加载 Token
    func loadAccessToken(code : String,finished : HMNetFinishedCallBack ){
    let urlstring = "https://api.weibo.com/oauth2/access_token"
        let params = ["client_id" :clientId ,
        "client_secret" : appSecret,
        "grant_type" :"authorization_code" ,
        "code" :code ,//用户注册的新浪微博的帐号,得到的code的返回值的情况
        "redirect_uri" : redirectUri,
        ]
    request(HMNetWorkMethod.POST, urlString: urlstring, pragma: params, finished: finished)
    }
    //MARK:-封装AFN网络的方法,便于替换网络的访问的方法,第三方框架的网络代码都集中在这里;
    /// AFN 的 request 的整体的方法的封装
    ///
    /// - parameter Method:    GET 和 POST
    /// - parameter urlString: 加载用户的地址
    /// - parameter pragma:    用户字典
    /// - parameter finished:  完成的回调
    private func request(Method :HMNetWorkMethod,  urlString : String,pragma : [String : AnyObject ],finished : HMNetFinishedCallBack){
    //1.定义成功的闭包
        let successCallBack:(NSURLSessionDataTask!,AnyObject!) ->Void = { (_ , JOSN) -> Void in
            if let result = JOSN as? [String : AnyObject ]{
                //有结果的回调
                finished(result: result, error: nil)
            }else{
                //没有错误,同时没有结果
                print("没有数据")
                
                let error = NSError(domain:HMErrorDomainName , code: -1, userInfo:["errorMessage":"空数据"] )
                finished(result: nil, error: error)
            }
        }
    //2.定义失败的闭包
        let failedCallBack:(NSURLSessionDataTask!,NSError!)->Void = { (_ , error ) -> Void in
            print(error )
            finished(result: nil, error: error )
        }
    //3.根据method 来选择执行的方法
        switch Method{
        case.GET:GET(urlString, parameters: pragma, success: successCallBack, failure: failedCallBack)
        case.POST:POST(urlString, parameters: pragma, success: successCallBack, failure: failedCallBack)
        }
    }
    //网络的访问的类型的别名;
    typealias HMNetFinishedCallBack = (result :[String : AnyObject]?,error : NSError?)->()
}
